﻿using System.Windows;
using System.Windows.Controls;
using System.Windows.Media;
using ThePresenter.Windows.Ink;
using ThePresenter.Windows.Input;

namespace ThePresenter.Windows.Controls
{
	/// <summary>
	/// Interaction logic for DrawingProperties.xaml
	/// </summary>
	public partial class DrawingProperties : UserControl
	{
		#region Dependency property identifiers

		/// <summary>
		/// Identifies the <see cref="BrushColor"/> dependency property.
		/// </summary>
		/// <value>The identifier for the <see cref="BrushColor"/> dependency property.</value>
		public static readonly DependencyProperty BrushColorProperty = DependencyProperty.Register("BrushColor", typeof(SolidColorBrush), typeof(DrawingProperties), new UIPropertyMetadata(Brushes.Black, new PropertyChangedCallback(OnBrushColorChanged)));

		/// <summary>
		/// Identifies the <see cref="BrushThickness"/> dependency property.
		/// </summary>
		/// <value>The identifier for the <see cref="BrushThickness"/> dependency property.</value>
		public static readonly DependencyProperty BrushThicknessProperty = DependencyProperty.Register("BrushThickness", typeof(double), typeof(DrawingProperties), new UIPropertyMetadata(2d, new PropertyChangedCallback(OnBrushThicknessChanged)));

		/// <summary>
		/// Identifies the <see cref="IsHighlighter"/> dependency property.
		/// </summary>
		/// <value>The identifier for the <see cref="IsHighlighter"/> dependency property.</value>
		public static readonly DependencyProperty IsHighlighterProperty = DependencyProperty.Register("IsHighlighter", typeof(bool), typeof(DrawingProperties), new UIPropertyMetadata(new PropertyChangedCallback(OnIsHighlighterChanged)));

		/// <summary>
		/// Identifies the <see cref="EditingMode"/> dependency property.
		/// </summary>
		/// <value>The identifier for the <see cref="EditingMode"/> dependency property.</value>
		public static readonly DependencyProperty EditingModeProperty = DependencyProperty.Register("EditingMode", typeof(InkCanvasEditingMode), typeof(DrawingProperties), new UIPropertyMetadata(InkCanvasEditingMode.Ink, new PropertyChangedCallback(OnEditingModeChanged)));

		/// <summary>
		/// Identifies the <see cref="SelectedTool"/> dependency property.
		/// </summary>
		/// <value>The identifier for the <see cref="SelectedTool"/> dependency property.</value>
		public static readonly DependencyProperty SelectedToolProperty = DependencyProperty.Register("SelectedTool", typeof(InkCanvasTool), typeof(DrawingProperties), new UIPropertyMetadata(InkCanvasTool.Pen, new PropertyChangedCallback(OnSelectedToolChanged)));

		#endregion

		#region Properties

		/// <summary>
		/// Gets or sets the color of the brush. This is a dependency property.
		/// </summary>
		/// <value>The color of the brush.</value>
		public SolidColorBrush BrushColor
		{
			get
			{
				return (SolidColorBrush)GetValue(BrushColorProperty);
			}
			set
			{
				SetValue(BrushColorProperty, value);
			}
		}

		/// <summary>
		/// Gets or sets the thickness of the brush. This is a dependency property.
		/// </summary>
		/// <value>The thickness of the brush.</value>
		public double BrushThickness
		{
			get
			{
				return (double)GetValue(BrushThicknessProperty);
			}
			set
			{
				SetValue(BrushThicknessProperty, value);
			}
		}

		/// <summary>
		/// Gets or sets the is highlighter. This is a dependency property.
		/// </summary>
		/// <value>The is highlighter.</value>
		public bool IsHighlighter
		{
			get
			{
				return (bool)GetValue(IsHighlighterProperty);
			}
			set
			{
				SetValue(IsHighlighterProperty, value);
			}
		}

		/// <summary>
		/// Gets or sets the editing mode. This is a dependency property.
		/// </summary>
		/// <value>The editing mode.</value>
		public InkCanvasEditingMode EditingMode
		{
			get
			{
				return (InkCanvasEditingMode)GetValue(EditingModeProperty);
			}
			set
			{
				SetValue(EditingModeProperty, value);
			}
		}

		/// <summary>
		/// Gets or sets the selected tool. This is a dependency property.
		/// </summary>
		/// <value>The selected tool.</value>
		public InkCanvasTool SelectedTool
		{
			get
			{
				return (InkCanvasTool)GetValue(SelectedToolProperty);
			}
			set
			{
				SetValue(SelectedToolProperty, value);
			}
		}

		#endregion
		
		#region Constructors

		/// <summary>
		/// Initializes a new instance of the <see cref="DrawingProperties"/> class.
		/// </summary>
		public DrawingProperties()
		{
			InitializeComponent();
		}

		#endregion

		#region Methods

		/// <summary>
		/// Called when brush color is changed.
		/// </summary>
		/// <param name="property">The property.</param>
		/// <param name="args">The <see cref="System.Windows.DependencyPropertyChangedEventArgs"/> instance containing the event data.</param>
		static void OnBrushColorChanged(DependencyObject property, DependencyPropertyChangedEventArgs args)
		{
			DrawingProperties This = property as DrawingProperties;
			var value = args.NewValue as SolidColorBrush;

			DrawingPropertiesCommands.SetBrushColor.Execute(value, This);
		}

		/// <summary>
		/// Called when brush thickness is changed.
		/// </summary>
		/// <param name="property">The property.</param>
		/// <param name="args">The <see cref="System.Windows.DependencyPropertyChangedEventArgs"/> instance containing the event data.</param>
		static void OnBrushThicknessChanged(DependencyObject property, DependencyPropertyChangedEventArgs args)
		{
			DrawingProperties This = property as DrawingProperties;
			double value = (double)args.NewValue;

			DrawingPropertiesCommands.SetBrushThickness.Execute(value, This);
		}

		/// <summary>
		/// Called when is highlighter is changed.
		/// </summary>
		/// <param name="property">The property.</param>
		/// <param name="args">The <see cref="System.Windows.DependencyPropertyChangedEventArgs"/> instance containing the event data.</param>
		static void OnIsHighlighterChanged(DependencyObject property, DependencyPropertyChangedEventArgs args)
		{
			DrawingProperties This = property as DrawingProperties;
			bool value = (bool)args.NewValue;

			DrawingPropertiesCommands.SetIsHighlighter.Execute(value, This);
		}

		/// <summary>
		/// Called when editing mode is changed.
		/// </summary>
		/// <param name="property">The property.</param>
		/// <param name="args">The <see cref="System.Windows.DependencyPropertyChangedEventArgs"/> instance containing the event data.</param>
		static void OnEditingModeChanged(DependencyObject property, DependencyPropertyChangedEventArgs args)
		{
			DrawingProperties This = property as DrawingProperties;
			InkCanvasEditingMode value = (InkCanvasEditingMode)args.NewValue;

			DrawingPropertiesCommands.SetEditingMode.Execute(value, This);
		}

		/// <summary>
		/// Called when selected tool changed.
		/// </summary>
		/// <param name="property">The property.</param>
		/// <param name="args">The <see cref="System.Windows.DependencyPropertyChangedEventArgs"/> instance containing the event data.</param>
		static void OnSelectedToolChanged(DependencyObject property, DependencyPropertyChangedEventArgs args)
		{
			DrawingProperties This = property as DrawingProperties;
			InkCanvasTool value = (InkCanvasTool)args.NewValue;

			switch (value)
			{
				case InkCanvasTool.None:
					This.EditingMode = InkCanvasEditingMode.None;
					break;

				case InkCanvasTool.Pen:
					This.EditingMode = InkCanvasEditingMode.Ink;
					This.IsHighlighter = false;
					break;

				case InkCanvasTool.Highlighter:
					This.EditingMode = InkCanvasEditingMode.Ink;
					This.IsHighlighter = true;
					break;

				case InkCanvasTool.Select:
					This.EditingMode = InkCanvasEditingMode.Select;
					break;

				case InkCanvasTool.EraseByPoint:
					This.EditingMode = InkCanvasEditingMode.EraseByPoint;
					break;

				case InkCanvasTool.EraseByStroke:
					This.EditingMode = InkCanvasEditingMode.EraseByStroke;
					break;
			}
		}

		#endregion
	}
}
